#ifndef _VM_H
#define _VM_H
#include <defs.h>

struct pgtblEntry_bit{
    uint64 V: 1;
    uint64 R: 1;
    uint64 W: 1;
    uint64 X: 1;
    uint64 U: 1;
    uint64 G: 1;
    uint64 A: 1;
    uint64 D: 1;
    uint64 RSW: 2;
    uint64 ppn: 26;
    uint64 reserved: 28;
};

struct va_bit
{
    uint64 offset: 30;
    uint64 vpn: 9;
    uint64 high_bit : 25;
};


struct pa_bit
{
    uint64 offset: 30;
    uint64 ppn: 26;
    uint64 high_bit : 8;
};

uint64 GetBit(uint64 x, uint64 n)
{
    return (x >> n) & 1;
}
uint64 GetBitRange(uint64 x, uint64 n, uint64 m)
{
    return (x >> n) & ((1 << (m - n + 1)) - 1);
}
uint64 SetBit(uint64 x, uint64 n, uint64 v)
{
    return (x & ~(1 << n)) | (v << n);
}
uint64 SetBitRange(uint64 x, uint64 n, uint64 m, uint64 v)
{
    return (x & ~(((1 << (m - n + 1)) - 1) << n)) | (GetBitRange(v, 0, m - n) << n);
}

void create_mapping(uint64 *pgtbl, uint64 va, uint64 pa, uint64 sz, int perm);


#endif